from typing import Optional
from application.config import PROJECT_NAME, CAPTCHA_KEY
from application.util.RedisUtil import RedisUtil
from application.util.EmailUtil import send_email
from application.config.EmailConfig import EmailConfig
from application.enumeration.StatusCodeEnum import StatusCodeEnum
from application.enumeration.ContentTypeEnum import ContentTypeEnum
from application.enumeration.StatisticsTypeEnum import StatisticsTypeEnum
from application.model.StatisticsModel import StatisticsModel
from application.mapper.StatisticsMapper import StatisticsMapper
from application.exception.BasicException import BasicException
from application.util.StringUtil import generate_verification_code, is_valid_email, md5_encode

# 实例化redis客户端
redis_client: RedisUtil = RedisUtil()


async def add_statistics(target_id: int, content_type: ContentTypeEnum, statistics_type: StatisticsTypeEnum) -> None:
    """
    添加统计
    :param target_id: 目标ID
    :param content_type: 内容类型
    :param statistics_type: 统计类型
    :return:
    """
    statistics_model: Optional[StatisticsModel] = await StatisticsMapper.get_data_by_field(target_id=target_id,
                                                                                           content_type=content_type,
                                                                                           name=statistics_type)
    # 如果没有该统计记录，则新增，数量设置为 1
    if not statistics_model:
        await StatisticsMapper.insert(data=dict(target_id=target_id, content_type=content_type,
                                                name=statistics_type, quantity=1))
    else:  # 如果有该统计记录，则数量加 1
        statistics_model.quantity += 1


def create_avatar() -> None:
    """
    在图片表里生成默认头像
    :return:
    """
    import pymysql
    import time
    from pymysql.cursors import Cursor
    from pymysql import Connect
    from application.config.DatabaseConfig import MysqlConfig
    # 头像URL
    url: str = "https://c-ssl.duitang.com/uploads/blog/202206/12/20220612164733_72d8b.jpg"
    md5_index: str = md5_encode(url)  # 默认头像的md5_index
    # 创建数据库链接
    connect: Connect = pymysql.connect(host=MysqlConfig.host, port=MysqlConfig.port, user=MysqlConfig.username,
                                       password=MysqlConfig.password, db=MysqlConfig.database_name)
    cursor: Cursor = connect.cursor()
    while True:
        try:
            # 插入数据
            cursor.execute(f"INSERT INTO image(`md5`, `url`) VALUES ('{md5_index}', '{url}');")
            connect.commit()
            break
        except Exception:
            time.sleep(1)
    # 关闭链接
    cursor.close()
    connect.close()


def email_captcha(email: str) -> None:
    """
    发送邮箱验证码
    :param email: 目标邮箱
    :return:
    """
    # Redis的Key
    redis_key: str = CAPTCHA_KEY + email
    if redis_client.get_value(key=redis_key) is not None:
        raise BasicException(status_code=StatusCodeEnum.ILLEGALITY_ERROR.value,
                             message="已发送验证码，未找到请查看垃圾箱！")
    # 检查邮箱格式
    if not is_valid_email(text=email):
        raise BasicException(status_code=StatusCodeEnum.BAD_REQUEST_ERROR.value, message="请输入正确邮箱")
    code: str = generate_verification_code()  # 生成验证码
    # 发送邮件
    result: bool = send_email(target_email=email, title=f"[{PROJECT_NAME}] 邮箱验证码",
                              content=f"您的验证码是：{code}，"
                                      f"{int(EmailConfig.email_code_expire // 60)}分钟内有效")
    # 发送失败
    if not result:
        raise BasicException(status_code=StatusCodeEnum.ERROR.value, message="验证码发送失败，请稍后再试")
    # 保存验证码到redis
    redis_client.set_value(key=redis_key, value=code, ex=EmailConfig.email_code_expire)
